package controller

import (
	"awesomeProject/lib"
	"github.com/gin-gonic/gin"
	"log"
)

func SearchFriend(c *gin.Context) {
	var req lib.SearchFriendReq
	if err := c.ShouldBindJSON(&req); err != nil {
		log.Println("read json fail in search friend")
		return
	}
	ok, err := AuthId(req.SelfId, req.Token)
	log.Println(req.SelfId, req.Token)
	if !ok || err != nil {
		log.Println("auth fail in search friend")
		return
	}
	typeCode := req.SearchTypeCode
	var user lib.User
	if typeCode == 1 {
		id := req.Id
		user, ok, err = SearchId(id)
		if !ok || err != nil {
			log.Println("user id invalid")
			c.JSON(200, lib.SearchFriendResp{
				StatusCode: 1,
				StatusMsg:  "user id invalid",
			})
			return
		}
	} else {
		username := req.Username
		user, ok, err = SearchUsername(username)
		if !ok || err != nil {
			log.Println("username invalid")
			c.JSON(200, lib.SearchFriendResp{
				StatusCode: 1,
				StatusMsg:  "username invalid",
			})
			return
		}
	}
	ok = isFriend(req.SelfId, user.Id)
	resp := lib.SearchFriendResp{
		StatusCode:   2,
		StatusMsg:    "search friend successfully",
		IsFriendCode: 1,
		User:         user,
	}
	if !ok {
		resp.IsFriendCode = 0
	}
	c.JSON(200, resp)
	return
}

func isFriend(id_1 int64, id_2 int64) bool {
	rows, err := pool.Query("select id_2 from public.relation where id_1=$1", id_1)
	if err != nil {
		log.Println("id_1 invalid in isfriend")
		return false
	}
	var idRef int64
	for rows.Next() {
		if err := rows.Scan(&idRef); err != nil {
			log.Println("database fail in isfriend")
			return false
		}
		if idRef == id_2 {
			return true
		}
	}
	return false
}

func AddFriend(c *gin.Context) {
	var req lib.AddFriendReq
	if err := c.ShouldBindJSON(&req); err != nil {
		log.Println("read json fail in add friend")
		return
	}
	sender := req.Sender
	ok, err := AuthId(sender.Id, req.Token)
	if !ok || err != nil {
		log.Println("auth fail in add friend, id or token invalid")
		return
	}
	ok = isFriend(sender.Id, req.ReceiverId)
	if ok {
		log.Println("you are already friend, or the receiver isn't exist")
		c.JSON(200, lib.AddFriendResp{
			StatusCode: 1,
			StatusMsg:  "你们已经是好友",
		})
		return
	}
	targetConn, ok := clients[req.ReceiverId]
	if !ok {
		log.Println("receiver id invalid or receiver is offline")
		if err := StoreFrdReq(req); err != nil {
			log.Println("store the friend request fail")
			c.JSON(200, lib.AddFriendResp{
				StatusCode: 1,
				StatusMsg:  "maybe the receiver id is invalid",
			})
			return
		}
		c.JSON(200, lib.AddFriendResp{
			StatusCode: 2,
			StatusMsg:  "receiver is offline, we will resend the request automatically when the receiver is online",
		})

		return
	}
	if err := targetConn.WriteJSON(lib.GetFriendReqMsg{
		Sender: sender,
		Brief:  req.Brief,
		SelfId: req.ReceiverId,
		Type:   "add_friend",
	}); err != nil {
		log.Println("write json fail to targetconn in add friend")
		c.JSON(200, lib.AddFriendResp{
			StatusCode: 0,
			StatusMsg:  "send fail, maybe receiver is offline",
		})
		return
	}
	c.JSON(200, lib.AddFriendResp{
		StatusCode: 2,
		StatusMsg:  "send request successfully",
	})
	return
}
